package com.battle.service.service.impl;

import cn.afterturn.easypoi.excel.ExcelImportUtil;
import cn.afterturn.easypoi.excel.entity.ImportParams;
import cn.hutool.core.collection.CollectionUtil;
import com.alibaba.druid.util.StringUtils;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.battle.pojo.entity.PersonWarCase;
import com.battle.pojo.entity.TrainingAchievement;
import com.battle.pojo.entity.TrainingAchievementDetails;
import com.battle.pojo.entity.User;
import com.battle.pojo.param.trainingAchievement.*;
import com.battle.pojo.vo.trainingAchievement.*;
import com.battle.pojo.dto.trainingAchievement.*;
import com.battle.service.repository.in.PersonWarCaseRepository;
import com.battle.service.repository.in.TrainingAchievementDetailsRepository;
import com.battle.service.repository.in.TrainingAchievementRepository;
import com.battle.service.repository.in.UserRepository;
import com.battle.service.service.in.TrainingAchievementService;
import com.battle.service.utils.FileUtil;
import nirvana.core.domains.vo.PageResult;
import nirvana.core.exceptions.BizException;
import nirvana.core.utils.ids.IdGenerator;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;


import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 【描 述】：培训成绩服务
 * 【环 境】：J2SE 17
 * 【详 细】：
 */
@Service
public class TrainingAchievementServiceImpl implements TrainingAchievementService {

    private final TrainingAchievementRepository trainingAchievementRepository;
    private final TrainingAchievementDetailsRepository detailsRepository;
    private final UserRepository userRepository;

    private final PersonWarCaseRepository personWarCaseRepository;

    public TrainingAchievementServiceImpl(TrainingAchievementRepository trainingAchievementRepository, TrainingAchievementDetailsRepository detailsRepository, UserRepository userRepository, PersonWarCaseRepository personWarCaseRepository) {
        this.trainingAchievementRepository = trainingAchievementRepository;
        this.detailsRepository = detailsRepository;
        this.userRepository = userRepository;
        this.personWarCaseRepository = personWarCaseRepository;
    }


    /**
     * 创建培训成绩
     *
     * @param param
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void createTrainingAchievement(CreateTrainingAchievementParam param) {
        TrainingAchievement trainingAchievement = new TrainingAchievement();
        BeanUtils.copyProperties(param, trainingAchievement);
        Long id = IdGenerator.SNOW.generate();
        trainingAchievement.setId(id);

        //拿到传入的表头
        JSONArray headers = param.getHeaders();
        trainingAchievement.setHeaderList(headers.toJSONString());

        //拿到传入的数据
        JSONArray data = param.getBodys();
        bathAddDetails(id,trainingAchievement,headers,data);
        if (!trainingAchievementRepository.save(trainingAchievement)){
            throw new BizException("保存失败");
        }
    }

    /**
     * 修改培训成绩
     * @param param
     */
    @Override
    public void editTrainingAchievement(EditTrainingAchievementParam param) {
        TrainingAchievement trainingAchievement = trainingAchievementRepository.getByIdCheck(param.getId());
        BeanUtils.copyProperties(param, trainingAchievement);

        //拿到传入的表头
        JSONArray headers = param.getHeaders();
        trainingAchievement.setHeaderList(headers.toJSONString());

        //拿到传入的数据
        JSONArray data = param.getBodys();

        bathAddDetails(param.getId(), trainingAchievement,headers,data);
        if (!trainingAchievementRepository.edit(trainingAchievement)){
            throw new BizException("保存失败");
        }
    }


    /**
     * 批量绑定培训成绩
     * @param trainingId
     * @param trainingAchievement
     * @param headers
     * @param bodys
     */
    void bathAddDetails(Long trainingId,TrainingAchievement trainingAchievement,JSONArray headers,JSONArray bodys){
        //根据培训id删除所有培训成绩
        List<TrainingAchievementDetails> deleteList = detailsRepository.getBaseMapper().selectList(new LambdaQueryWrapper<TrainingAchievementDetails>()
                .eq(TrainingAchievementDetails::getTrainingId, trainingId)
                .eq(TrainingAchievementDetails::getIsDelete, false));
        if (CollectionUtil.isNotEmpty(deleteList)){
            List<Long> ids = deleteList.stream().map(TrainingAchievementDetails::getId).distinct().collect(Collectors.toList());
            if (!detailsRepository.trueDeletionByIds(ids)){
                throw new BizException("删除失败");
            }
        }

        for (int i = 0; i < bodys.size(); i++) {
            JSONObject jsonObject = bodys.getJSONObject(i);

            TrainingAchievementDetails details = new TrainingAchievementDetails();
            details.setId(IdGenerator.SNOW.generate());
            details.setTrainingId(trainingId);
            details.setTrainingName(trainingAchievement.getName());
            details.setStartTime(trainingAchievement.getStartTime());
            details.setEndTime(trainingAchievement.getEndTime());

            //获取用户名固定字段 in0
            String name = jsonObject.getString("in0");
            //获取总分固定字段 in1
            BigDecimal totalScore = jsonObject.getBigDecimal("in1");

            //根据用户名称查询用户id
            PersonWarCase personWarCase = new PersonWarCase();
            personWarCase.setName(name);
            personWarCase.setIsDelete(false);
            personWarCase = personWarCaseRepository.getByEntity(personWarCase);
            if (personWarCase == null) {
                throw new BizException("人员名称：" + name + "不存在");
            }
            details.setPersonId(personWarCase.getId());
            details.setTotalScore(totalScore);
            details.setHeaderList(headers.toJSONString());
            details.setDataList(jsonObject.toJSONString());
            if (!detailsRepository.save(details)){
                throw new BizException("保存失败");
            }
        }
    }


    /**
     * 移除培训成绩
     *
     * @param id
     */
    @Override
    public void removeTrainingAchievement(Long id) {
        trainingAchievementRepository.removeById(id);
    }

    /**
     * 启动/禁用培训成绩
     *
     * @param id
     */
    @Override
    public void enabledTrainingAchievement(Long id) {
        TrainingAchievement trainingAchievement = trainingAchievementRepository.getByIdCheck(id);
        trainingAchievement.setIsDisable(!trainingAchievement.getIsDisable());
        trainingAchievementRepository.edit(trainingAchievement);
    }

    /**
     * 获取培训成绩详情
     *
     * @param id
     * @return
     */
    @Override
    public GetTrainingAchievementVo getTrainingAchievement(Long id) {
        TrainingAchievement trainingAchievement = trainingAchievementRepository.getByIdCheck(id);
        GetTrainingAchievementVo vo = new GetTrainingAchievementVo();
        BeanUtils.copyProperties(trainingAchievement, vo);

        //获取表头
        JSONArray headers = JSONArray.parseArray(trainingAchievement.getHeaderList());
        //获取表体
        JSONArray data = new JSONArray();

        List<TrainingAchievementDetails> trainingAchievementDetails = detailsRepository.getBaseMapper().selectList(new LambdaQueryWrapper<TrainingAchievementDetails>()
                .eq(TrainingAchievementDetails::getTrainingId, id)
                .eq(TrainingAchievementDetails::getIsDelete, false));
        if (CollectionUtil.isNotEmpty(trainingAchievementDetails)){
            for (TrainingAchievementDetails details : trainingAchievementDetails) {
                JSONObject jsonObject = JSONObject.parseObject(details.getDataList());
                data.add(jsonObject);
            }
        }

        vo.setHeaders(headers);
        vo.setBodys(data);
        return vo;
    }

    /**
     * 获取培训成绩 列表
     *
     * @param param
     * @return
     */
    @Override
    public PageResult<GetTrainingAchievementListVo> getTrainingAchievementList(GetTrainingAchievementListParam param) {

        SelectTrainingAchievementDto dto = new SelectTrainingAchievementDto();
        BeanUtils.copyProperties(param, dto);
        Page<TrainingAchievement> page = trainingAchievementRepository.selectTrainingAchievement(dto);
        List<TrainingAchievement> trainingAchievementList = page.getRecords();
        List<GetTrainingAchievementListVo> list = new ArrayList<>();

        if (CollectionUtil.isNotEmpty(trainingAchievementList)) {
            List<Long> userIds = new ArrayList<>();

            trainingAchievementList.forEach(v -> {
                userIds.add(v.getCreator());
            });

            Map<Long, User> userMap = userRepository.getMap(userIds);

            for (TrainingAchievement trainingAchievement : trainingAchievementList) {
                GetTrainingAchievementListVo vo = new GetTrainingAchievementListVo();
                BeanUtils.copyProperties(trainingAchievement, vo);
                User operation = userMap.get(trainingAchievement.getCreator());
                if (operation != null) {
                    vo.setCreateName(operation.getName());
                }
                list.add(vo);
            }
        }


        return new PageResult<>(list, page);

    }

    /**
     * 获取培训成绩下拉列表
     *
     * @param param
     * @return
     */
    @Override
    public List<GetTrainingAchievementDownListVo> getTrainingAchievementDownList(GetTrainingAchievementDownListParam param) {
        TrainingAchievement po = new TrainingAchievement();
        if (param != null) {
            BeanUtils.copyProperties(param, po);
        }
        List<TrainingAchievement> trainingAchievementList = trainingAchievementRepository.getListByEntity(po);

        List<GetTrainingAchievementDownListVo> list = new ArrayList<>();
        for (TrainingAchievement trainingAchievement : trainingAchievementList) {
            GetTrainingAchievementDownListVo vo = new GetTrainingAchievementDownListVo();
            BeanUtils.copyProperties(trainingAchievement, vo);
            list.add(vo);
        }
        return list;
    }

    /**
     * 导入
     * @param param
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void importTrainingAchievement(ImportTrainingAchievementParam param) throws IOException {
        StringBuffer error = new StringBuffer();

        TrainingAchievement trainingAchievement = new TrainingAchievement();
        BeanUtils.copyProperties(param,trainingAchievement);
        trainingAchievement.setId(IdGenerator.SNOW.generate());
        trainingAchievement.setUrl(param.getFileUrl());
        trainingAchievementRepository.save(trainingAchievement);

        InputStream inputStream =null;
        try {
            URL url=new URL(param.getFileUrl());
            URLConnection urlConnection = url.openConnection();
            inputStream=urlConnection.getInputStream();
            if (inputStream == null) {
                throw new BizException("文件不存在");
            }

            ImportParams params = new ImportParams();
            params.setTitleRows(0);
            params.setStartRows(0);

            List<EditTrainingAchievementParam> result = ExcelImportUtil.importExcel(inputStream, EditTrainingAchievementParam.class, params);
//            for (EditTrainingAchievementParam excel : result) {
//                PersonWarCase personWarCase = new PersonWarCase();
//                personWarCase.setName(excel.getPersonName());
//                personWarCase.setIsDelete(false);
//                personWarCase = personWarCaseRepository.getByEntity(personWarCase);
//                if (personWarCase == null) {
//                    error.append("人员名称：" + excel.getPersonName() + "不存在\n");
//                    continue;
//                } else {
//                    TrainingAchievementDetails details = new TrainingAchievementDetails();
//                    BeanUtils.copyProperties(excel, details);
//                    details.setId(IdGenerator.SNOW.generate());
//                    details.setPersonId(personWarCase.getId());
//                    details.setTrainingId(trainingAchievement.getId());
//                    details.setTrainingName(trainingAchievement.getName());
//                    details.setStartTime(trainingAchievement.getStartTime());
//                    details.setEndTime(trainingAchievement.getEndTime());
//                    detailsRepository.save(details);
//                }
//            }
        } catch (Exception e) {
            e.printStackTrace();
        }finally {
            inputStream.close();
        }

        if (!StringUtils.isEmpty(error.toString())) {
            throw new BizException(error.toString());
        }

    }


}



